<template>
  <div style="display: flex;flex-direction: column;gap: 10px;">
      <RandomCharacter />
      
      <!-- 类型过滤器和排序标签区域 -->
      <el-card class="panel-card filter-section">
       
        <div class="filter-controls">
          <div style="display: flex;gap:10px;">
                      <div class="sort-tags-container ml-4" v-if="sortedPanelIds.length > 0">
            <el-scrollbar ref="scrollbarRef" @wheel.prevent="onHandleScroll">
              <ul 
                class="sort-tags-list"
                :class="{ 'has-filter': selectedType }"
                ref="sortableContainer"
              >
                <li 
                  v-for="panelId in sortedPanelIds" 
                  :key="panelId"
                  class="sort-tag"
                  :data-panel-id="panelId"
                >
                  {{ exPromptStore.getRandomConfigByPanelId(panelId).class_type }}
                </li>
              </ul>
            </el-scrollbar>
          </div>
          <el-text class="mr2 vertical-middle">{{ $t('message.random.sortBy') }}:</el-text>
          </div>
        </div>
      </el-card>
      
      <!-- 按排序后的顺序渲染面板 -->
      <CommonPanelCard
        v-for="panelId in sortedPanelIds"
        :key="panelId"
        :panel-id="panelId"
        @on-random="getCommonRandom"
        @on-clear="handleClear"
        @on-more-action="handleMoreAction"
        @on-prev="handlePrevItem"
        @on-next="handleNextItem"
        @on-remove="handleRemovePanel"
      />
      
      <!-- 其他内容保持不变 -->
      <el-card class="panel-card">
        <div class="card-header">
          <el-text class="mr5">{{ $t('message.random.randomTag') }}</el-text>
          <el-text type="info">{{ $t('message.random.randomTagTip') }}</el-text>
        </div>
        <RandomTagGenerator :random="state.random" @tags-generated="handleRandomTagsGenerated" />
      </el-card>
      
      <el-card class="panel-card">
        <LoraLoader />
      </el-card>
      <el-upload
        v-show="false"
        ref="imageUploader"
        action=""
        :show-file-list="false"
        :before-upload="beforeImageUpload"
        accept="image/*"
      >
      </el-upload>
    </div>
</template>

<script lang="ts" setup>
import { computed, defineAsyncComponent, onMounted, reactive, ref, watch, nextTick, onUnmounted } from 'vue';
import { useConfigStore } from '@renderer/stores/configStore';
import { useExPrompt } from '@renderer/stores/useExPrompt';
import { ElMessage } from 'element-plus';
import { useGenerationStore } from '@renderer/stores/useGenerationStore';
import { commonApi } from '@renderer/api/common';
import RandomCharacter from '@renderer/views/random/component/RandomCharacter.vue';
import { ipcService } from '@renderer/services/ipcService';
import CommonPanelCard from './component/CommonPanelCard.vue';
import type { PromptItem, RandomConfig } from '@renderer/stores/useExPrompt';
import Sortable from 'sortablejs'; // 引入Sortable.js
import { Session } from '@renderer/utils/storage'; // 假设存在此工具类

defineOptions({ name: 'RandomPanel' });

// 类型定义
interface AdjacentItemParams {
  current_id: string;
  direction: 'prev' | 'next';
  value?: number[];
  class_type: string;
}

// 异步组件
const RandomTagGenerator = defineAsyncComponent(() => import("./component/RandomTag.vue"));
const LoraLoader = defineAsyncComponent(() => import("./component/LoraLoader.vue"));

// 状态管理
const exPromptStore = useExPrompt();
const generationStore = useGenerationStore();
const configStore = useConfigStore();
const selectedType = ref('');

// 排序相关状态
const sortedPanelIds = ref<string[]>([]); // 存储排序后的panelId
const sortableContainer = ref<HTMLElement | null>(null); // 排序容器
const scrollbarRef = ref<any>(null); // 滚动条引用
const sortableInstance = ref<Sortable | null>(null); // Sortable实例

const state = reactive({
  random: {
    tags: ''
  },
});

// 过滤后的项目
const filteredItems = computed<PromptItem[]>(() => {
  if (!selectedType.value) return exPromptStore.items;
  return exPromptStore.getItemsByType(selectedType.value);
});

// 初始化排序
const initializeSortOrder = () => {
  // 从Session加载保存的排序，没有则使用过滤后的顺序
  const savedOrder = Session.get(`sortedPanelIds_${selectedType.value || 'all'}`);
  if (savedOrder && Array.isArray(savedOrder)) {
    // 过滤掉已删除的面板ID
    sortedPanelIds.value = savedOrder.filter(id => 
      filteredItems.value.some(item => item.panelId === id)
    );
    
    // 如果有新添加的面板，追加到末尾
    filteredItems.value.forEach(item => {
      if (!sortedPanelIds.value.includes(item.panelId)) {
        sortedPanelIds.value.push(item.panelId);
      }
    });
  } else {
    // 初始排序为过滤后的项目顺序
    sortedPanelIds.value = filteredItems.value.map(item => item.panelId);
  }
  
  // 初始化或重新初始化Sortable
  nextTick(() => {
    initSortable();
  });
};

// 初始化Sortable
const initSortable = () => {
  if (!sortableContainer.value) return;
  
  // 销毁现有实例
  if (sortableInstance.value) {
    sortableInstance.value.destroy();
  }
  
  // 创建新的Sortable实例
  sortableInstance.value = Sortable.create(sortableContainer.value, {
    animation: 150, // 动画持续时间
    delay: 100, // 延迟开始拖拽，防止误触
    delayOnTouchOnly: true, // 仅在触摸设备上延迟
    handle: '.sort-tag', // 拖拽手柄
    ghostClass: 'sort-tag-ghost', // 拖拽时的占位元素类
    chosenClass: 'sort-tag-chosen', // 选中元素类
    dragClass: 'sort-tag-dragging', // 拖拽元素类
    dataIdAttr: 'data-panel-id', // 用于标识元素的属性
    
    // 开始拖拽时
    onStart: () => {
      sortableContainer.value?.classList.add('sorting-active');
    },
    
    // 拖拽结束时
    onEnd: (evt) => {
      sortableContainer.value?.classList.remove('sorting-active');
      
      // 更新排序数组
      const newOrder = [...sortedPanelIds.value];
      const [movedItem] = newOrder.splice(evt.oldIndex, 1);
      newOrder.splice(evt.newIndex, 0, movedItem);
      sortedPanelIds.value = newOrder;
      
      // 保存排序到Session
      Session.set(`sortedPanelIds_${selectedType.value || 'all'}`, newOrder);
      
      ElMessage.success('排序已更新');
    }
  });
};

// 当过滤条件变化时重新初始化排序
watch(
  () => filteredItems.value,
  () => {
    initializeSortOrder();
  },
  { immediate: true }
);

// 鼠标滚轮滚动处理
const onHandleScroll = (e: WheelEvent) => {
  if (scrollbarRef.value?.$refs?.wrapRef) {
    scrollbarRef.value.$refs.wrapRef.scrollLeft += e.deltaY > 0 ? 50 : -50;
  }
};

// 根据panelId获取项目
const getItemByPanelId = (panelId: string): PromptItem | undefined => {
  return exPromptStore.items.find(item => item.panelId === panelId);
};

// 获取标签显示文本
const getTagLabel = (panelId: string): string => {
  const item = getItemByPanelId(panelId);
  if (!item) return '';
  
  // 优先显示自定义名称，没有则显示类型
  return item.customize_name || item.type;
};

// 处理类型过滤变化
const handleTypeFilterChange = () => {
  // 过滤变化时会触发watch重新初始化排序
};

// 处理随机数据
const getCommonRandom = async (panelId: string, type: string) => {
  const search = exPromptStore.getRandomConfigByPanelId(panelId);
  const res = await commonApi().getRandomChioce(search);
  const result = res.data.result;
  const tags = result.tags.split('Negative prompt')[0];

  exPromptStore.updateItemByPanelId({
    panelId,
    type,
    ...result,
    tags,
  });
};

// 处理相邻项目
const getAdjacentPromptItem = async (panelId: string, type: string, params: AdjacentItemParams) => {
  try {
    const response = await commonApi().getAdjacentPromptItem(params);
    if (!response.data.result) return null;

    const result = response.data.result;
    const tags = result.tags ? result.tags.split('Negative prompt')[0] : '';

    exPromptStore.updateItemByPanelId({
      panelId,
      type,
      ...result,
      tags,
    });
    return result;
  } catch (error) {
    return null;
  }
};

// 上一个项目
const handlePrevItem = async (panelId: string, type: string) => {
  const item = getItemByPanelId(panelId);
  if (!item) return;
  
  const config = exPromptStore.getRandomConfigByPanelId(panelId);
  await getAdjacentPromptItem(panelId, type, {
    current_id: item.id,
    direction: 'prev',
    value: config.value,
    class_type: type,
  });
};

// 下一个项目
const handleNextItem = async (panelId: string, type: string) => {
  const item = getItemByPanelId(panelId);
  if (!item) return;
  
  const config = exPromptStore.getRandomConfigByPanelId(panelId);
  await getAdjacentPromptItem(panelId, type, {
    current_id: item.id,
    direction: 'next',
    value: config.value,
    class_type: type,
  });
};

// 清空面板
const handleClear = (panelId: string) => {
  exPromptStore.clearItemByPanelId(panelId);
};

// 更多操作
const handleMoreAction = (panelId: string, type: string, action: string) => {
  const item = getItemByPanelId(panelId);
  if (!item) return;

  switch (action) {
    case 'copy':
      handleCopy(item.tags);
      break;
    case 'update-image':
      //handleUpdatePromptImage(item);
      currentItemId.value = item.id
      nextTick(() => {
        imageUploader.value?.$el.querySelector('input[type="file"]')?.click();
      });
      break;
    case 'update-item':
      handleUpdatePromptItem(item);
      break;
  }
};

// 移除面板
const handleRemovePanel = (panelId: string) => {
  const success = exPromptStore.removeItemByPanelId(panelId);
  if (success) {
    // 从排序数组中移除
    sortedPanelIds.value = sortedPanelIds.value.filter(id => id !== panelId);
    // 更新Session中的排序
    Session.set(`sortedPanelIds_${selectedType.value || 'all'}`, sortedPanelIds.value);
    ElMessage.success('已移除面板');
  } else {
    ElMessage.warning('默认类型至少保留一个实例');
  }
};

// 处理图片更新
const handleUpdatePromptImage = async (item: PromptItem) => {
  const webpData = await configStore.convertToWebpV2(generationStore.previewImage);
  try {
    const result = await ipcService.saveBase64Image({
      base64Data: webpData,
      directory: 'collections',
      fileName: `${item.panelId}.webp`,
      imagesPath: configStore.config.imagesPath
    });
    if (result.success) {
      ElMessage.success('图片保存成功');
    } else {
      ElMessage.warning('图片保存失败');
    }
  } catch (error) {
    ElMessage.error(`图片保存失败: ${error.message}`);
  }
};

// 更新项目
const handleUpdatePromptItem = (item: PromptItem) => {
  if (item.id) {
    commonApi().updatePromptItem(item).then(res => {
      ElMessage.info(JSON.stringify(res.data));
    });
  } else {
    ElMessage.error("对象 ID 不能为空");
  }
};

// 复制内容
const handleCopy = async (content: string) => {
  try {
    await navigator.clipboard.writeText(content);
    ElMessage.success('标签已复制到剪贴板');
  } catch (err) {
    ElMessage.error('复制失败，请检查权限');
  }
};

// 处理随机标签生成
const handleRandomTagsGenerated = (value: string) => {
  exPromptStore.setRandomTag(value);
};

const imageUploader = ref();
const currentItemId = ref('');

const beforeImageUpload = async (file: File) => {
  try {
    if (!['image/jpeg', 'image/png', 'image/jpg'].includes(file.type)) {
      ElMessage.error('仅支持 JPG/JPEG/PNG 格式')
      return false
    }

    if (file.size > 5 * 1024 * 1024) {
      ElMessage.error('文件大小不能超过5MB')
      return false
    }
    handleReplaceImage(currentItemId.value,file);
    return false;
  } catch (error) {
    ElMessage.error(`转换失败: ${error.message}`)
    return false
  }
}

const handleReplaceImage = async (id:string,file:File)=>{
  try {
    const imageSave = `${configStore.config.imagesPath}\\collections\\${id}.webp`
    const result = await ipcService.saveWebpImage(
      file,
      imageSave,
    )
    if (result.success) {
      configStore.updateImageVersion(imageSave);
      ElMessage.success('图片保存成功');
    } else {
      ElMessage.warning('图片保存失败，但记录已创建');
    }
  } catch (error) {
    ElMessage.error(`图片保存失败: ${error.message}`);
  }
}

// 组件卸载时销毁Sortable实例
onUnmounted(() => {
  if (sortableInstance.value) {
    sortableInstance.value.destroy();
  }
});

onMounted(() => {
  initializeSortOrder();
});
</script>

<style lang="scss" scoped>
.sort-tags-container {
  display: flex;
  align-items: center;
  flex-wrap: wrap;
  flex: 1;
  min-width: 300px;
  max-width: calc(100% - 200px);
}

// 滚动条容器
:deep(.el-scrollbar) {
  width: 100%;
  .el-scrollbar__wrap {
    white-space: nowrap;
    overflow-x: auto;
    overflow-y: hidden;
    padding-bottom: 5px;
  }
}

.sort-tags-list {
  display: inline-flex;
  gap: 8px;
  padding: 5px 0;
  margin: 0;
  list-style: none;
}

.sort-tag {
  background-color: var(--el-color-primary-light-9);
  color: var(--el-color-primary);
  padding: 4px 10px;
  border-radius: 16px;
  font-size: 12px;
  cursor: grab;
  display: inline-flex;
  align-items: center;
  gap: 4px;
  transition: all 0.2s ease;
  border: 1px solid transparent;
  user-select: none;
  
  &:hover {
    background-color: var(--el-color-primary-light-8);
  }
  
  &:active {
    cursor: grabbing;
  }
}

// Sortable相关样式
.sort-tag-ghost {
  opacity: 0.5;
  background-color: var(--el-color-primary-light-7);
}

.sort-tag-chosen {
  background-color: var(--el-color-primary-light-7);
  box-shadow: 0 0 0 2px var(--el-color-primary);
}

.sort-tag-dragging {
  opacity: 0.8;
  transform: scale(1.05);
  box-shadow: 0 4px 12px rgba(0, 0, 0, 0.15);
  z-index: 100;
}

.sorting-active {
  // 排序过程中的容器样式
}

.drag-icon {
  font-size: 12px;
  opacity: 0.7;
  margin-left: 4px;
}

.vertical-middle {
  vertical-align: middle;
}

</style>
    